/******************************************************************************
 * $Id: defines.h,v 1.71 2005/07/11 22:39:22 jimb Exp $
 * @file
 * @author  Jim Brooks http://www.jimbrooks.org
 * @brief   Definitions, macros, enums.
 ******************************************************************************/

#ifndef DEFINES_H
#define DEFINES_H

#define LICENSE_BRIEF_STR		"GNU GPL no warranty"

#define HYPERSRC_OLD_VER_STRING "5.4.18"
#define HYPERSRC_VERSION_STRING	"6.0-beta1"
#define HYPERSRC_TITLE_STRING	"hypersrc "         \
               HYPERSRC_VERSION_STRING                       \
               " (c) Jim E. Brooks www.jimbrooks.org/hypersrc/ built: " \
               __DATE__ " "                                                     \
               __TIME__ " "                                                     \
               LICENSE_BRIEF_STR

#define CHAR_LF	'\n'
#define CHAR_CR	'\r'

/* for module_t.lineEnding */
#define ENDING_LF    LF
#define ENDING_CR   CR
#define ENDING_CRLF (LF+CR)

#define ENABLE_CHOOSER 1
// lv
#define PACKAGE_NAME "hypersrc"
#define LOCALEDIR "/usr/share/locale" // "mo"

#define IMAGE_DIR "/usr/share/pixmaps/hypersrc/"

#ifndef TRUE
#define TRUE 1
#endif
#ifndef FALSE
#define FALSE 0
#endif

/*
 * Geoms of widgets.
 */
#define PANED_WIDTH_HORZ				350 //780		/* < 800x600 for typical notebook computers */
#define PANED_WIDTH_VERT				300 //460
#define WIDGET_TAGS_CLIST_WIDTH_HORZ	280
#define WIDGET_TAGS_CLIST_WIDTH_VERT	240
#define WIDGET_MODULES_CLIST_WIDTH_HORZ (WIDGET_TAGS_CLIST_WIDTH_HORZ)
#define WIDGET_MODULES_CLIST_WIDTH_VERT (WIDGET_TAGS_CLIST_WIDTH_VERT)
#define WIDGET_TAGS_CLIST_WIDTH_COL0	115
#define WIDGET_TAGS_CLIST_WIDTH_COL1	55
#define WIDGET_TAGS_CLIST_WIDTH_COL2	45
#define WIDGET_TAGS_CLIST_WIDTH_COL3	20
#define WIDGET_HISTORY_CLIST_WIDTH_COL0	130
#define WIDGET_HISTORY_CLIST_WIDTH_COL1	36
#define WIDGET_HISTORY_CLIST_WIDTH_COL2	60
#define WIDGET_HISTORY_CLIST_WIDTH_COL3	20
#define WIDGET_MODULES_CLIST_WIDTH_COL0	178
#define WIDGET_MODULES_CLIST_WIDTH_COL1	80
#define WIDGET_FOUND_CLIST_WIDTH_COL0	90
#define WIDGET_FOUND_CLIST_WIDTH_COL1	90
#define WIDGET_FOUND_CLIST_WIDTH_COL2	60

/*
 * Maximums.
 */
//#define MAX_CHARSET_NAME_LEN    20
#define MAX_MODULES_DEFAULT		( 50 *1000)
#define MAX_MODULES_ABSOLUTE	(200 *1000)
#define MAX_STRING_LEN			1024
#define MAX_SUBSTR_LEN			1024
#define MAX_LINE_LEN			1024
#define MAX_LINES				(30 *1000)
#define MAX_TEXT_BUFFER_LEN		(MAX_LINES * MAX_LINE_LEN)
#define MAX_HAYSTACK_LEN		(MAX_TEXT_BUFFER_LEN)
#define MAX_WORD_LEN            256
#define MAX_ID_LEN              64
#define MAX_CTAGS_LINE_LEN		1024
#define MAX_CTAGS_FIELD_LEN		200
#define MAX_TAG_NAME_LEN		(MAX_CTAGS_FIELD_LEN)
#define MAX_FILENAME_LEN		256
#define MAX_GEOM_X_Y			2000
#define MAX_GEOM_W_H			2000
#define MAX_LOOPS				10000000
#define MAX_DROP_DOWN_STRINGS	10
#define MAX_FONT_NAME_LEN		256
#define MAX_HILITE_BUFFER_LEN	250000 /*75000*/
#define MAX_REGEX_MATCH_LEN		(100 *MAX_LINE_LEN) /* allow spanning some lines */

/*
 * Tag maximums.
 *
 * Early in development of hypersrc, if the amount of tags
 * exceeded 15,000 then a vscrollbar failed to attach
 * the tags clist.  However, this problem has gone way.
 * GTK 1.2.3 and 1.2.8 are known to support up to 120,000 tags
 * in a clist.
 */
#define MAX_TAGS_DEFAULT				 (1000*1000)
#if 0 /* no longer impose hard limit on -max-tags */
#define MAX_TAGS_ABSOLUTE				 1000000
#define MAX_TAGS_ABSOLUTE_STRING        "1000000"
#endif

/*
 * Parser maximums.
 */
#define MAX_LINES_FUNC_ARGS       12
#define MAX_LINES_FUNC_ARGS_STR  "12"
#define MAX_FUNC_DEFS_IN_MODULE  1000
#if 0
#define MAX_DOUBLE_QUOTE_LEN     (10*1000) /* limiting strings caused more problems than it solved */
#endif

/*
 * Minimums.
 */
#define MIN_WIDGET_TAGS_CLIST_WIDTH_COL		16
#define MIN_DIALOG_GEOM_X					60
#define MIN_DIALOG_GEOM_Y					60
#define MIN_MAIN_WIDGET_WIDTH				100
#define MIN_MAIN_WIDGET_HEIGTH				100

/*
 * Defaults.
 */
#define DEFAULT_PANED_SLIDER_PERCENT_FUNC_TREE	65

/*
 * Counts.
 */
#define WIDGET_TAGS_CLIST_COLUMNS		4
#define WIDGET_MODULES_CLIST_COLUMNS	1
#define WIDGET_HISTORY_CLIST_COLUMNS	WIDGET_TAGS_CLIST_COLUMNS
#define WIDGET_FOUND_CLIST_COLUMNS		3

#define SORT_UNSORTED					0
#define SORT_TAG						1
#define SORT_TYPE						2
#define SORT_MODULE						3

#define TAGS_VERY_MANY					10000

/*
 * Colors of widgets.
 */
#define COLOR_FOCUS_BG_RED		0xa000				/* bg focus color (light blue) */
#define COLOR_FOCUS_BG_GREEN	0xc000
#define COLOR_FOCUS_BG_BLUE		0xfa00

#define COLOR_TEXT_WIDGET_TEXT_FG_RED	0x1000		/* fg color of text of text widget */
#define COLOR_TEXT_WIDGET_TEXT_FG_GREEN	0x1000
#define COLOR_TEXT_WIDGET_TEXT_FG_BLUE	0x1000

#define COLOR_TEXT_WIDGET_TEXT_BG_RED	0xffff		/* bg color of text of text widget */
#define COLOR_TEXT_WIDGET_TEXT_BG_GREEN	0xffff
#define COLOR_TEXT_WIDGET_TEXT_BG_BLUE	0xffff

#define COLOR_TEXT_WIDGET_SEL_FG_RED	0xf000		/* fg color of selection in text widget */
#define COLOR_TEXT_WIDGET_SEL_FG_GREEN	0xf000
#define COLOR_TEXT_WIDGET_SEL_FG_BLUE	0xf000

#define COLOR_TEXT_WIDGET_SEL_BG_RED	0xb000		/* bg color of selection in text widget */
#define COLOR_TEXT_WIDGET_SEL_BG_GREEN	0x1000
#define COLOR_TEXT_WIDGET_SEL_BG_BLUE	0x1000

#define COLOR_CLIST_WIDGET_TEXT_FG_RED	 0x1000		/* fg color of text of clist widgets */
#define COLOR_CLIST_WIDGET_TEXT_FG_GREEN 0x1000
#define COLOR_CLIST_WIDGET_TEXT_FG_BLUE	 0x1000

#define COLOR_CLIST_WIDGET_TEXT_BG_RED	 0xffff//0xc000		/* bg color of text of clist widgets */
#define COLOR_CLIST_WIDGET_TEXT_BG_GREEN 0xffff//0xc000
#define COLOR_CLIST_WIDGET_TEXT_BG_BLUE  0xffff//0xc000

#define COLOR_CLIST_WIDGET_SEL_FG_RED	0xf000		/* fg color of selection in clist widget */
#define COLOR_CLIST_WIDGET_SEL_FG_GREEN	0xf000
#define COLOR_CLIST_WIDGET_SEL_FG_BLUE	0xf000

#define COLOR_CLIST_WIDGET_SEL_BG_RED	0x0//0xb000		/* bg color of selection in clist widget */
#define COLOR_CLIST_WIDGET_SEL_BG_GREEN	0x0//0x1000
#define COLOR_CLIST_WIDGET_SEL_BG_BLUE	0xffff//0x1000

/*
 * Default fonts.
 */
#define FONT_NAME_TEXT_DEFAULT	"Bitstream Vera Sans Mono 11"
#define FONT_NAME_LIST_DEFAULT	"Sans 9"
#define FONT_NAME_TREE_DEFAULT	"Sans 9"

/*
 * Name of fonts used for hilites.
 */
#if 0
#define FONT_NAME_C_COMMENT		"lucidasans-italic-10"
#define FONT_NAME_C_KEYWORD		"-bitstream-courier-bold-r-normal--0-0-0-0-m-0-iso8859-1"
#define FONT_NAME_C_TYPE		"-bitstream-courier-medium-r-normal--0-0-0-0-m-0-iso8859-1"
#define FONT_NAME_C_SYMBOL		"-*-courier-bold-r-normal-*-16-*-*-*-*-*-*-*"
#else
#define FONT_NAME_C_COMMENT		"Sans 11"
#define FONT_NAME_C_KEYWORD		"Sans 11"
#define FONT_NAME_C_TYPE		"Sans 11"
#define FONT_NAME_C_SYMBOL		"Sans 11"
#endif

/*
 * Misc definitions.
 */
#define ROW_NONE				(-1)
#define UNIMPLEMENTED()			{ g_assert( 0 ); }
#define FONT_PROPORTIONAL		0
#define FONT_MONOSPACED			1
#define SCROLL_TEXT_VERT_FRAC	0.24
#define KLUDGE_IGNORED_GDK_KEY	GDK_F12
#define MOUSE_WHEEL_KEY_STR		"Left-Ctrl"

/*
 * Locking and callback definitions
 */
#define UNLOCKED			FALSE		/* for initializing a lock_t */
#define LOCKED				TRUE
#define CALLBACK_ID_OFF		0x7fffffff	/* GTK+ id of callback turned off */

/*
 * Offset for dialog widgets.
 */
#define DIALOG_X_OFFSET		200
#define DIALOG_Y_OFFSET		100

/*
 * A convention for integer return values is:
 * - A successful function returns zero             defined as FUNC_OK.
 * - A failing    function returns a negative value defined as FUNC_FAIL*.
 */
typedef
enum FUNC_X_
{
   FUNC_OK						=  0,
   FUNC_FAIL					= -1,	/* inspecific failure */
   FUNC_FAIL_NEGATIVE			= -1,	/* an explicit negative value */
   FUNC_FAIL_ABORT				= -2,	/* function had to abort */
   FUNC_FAIL_EXCESSIVE			= -3,	/* excessive iterations has occurred */
   FUNC_FAIL_TOO_MANY_MODULES	= -4
} FUNC_X;

/*
 * Enums for menu items.
 */
typedef
enum MENU_ITEM_
{
   MENU_ITEM_FILE_EXIT,

   MENU_ITEM_SORT_TAG,
   MENU_ITEM_SORT_MODULE,
   MENU_ITEM_SORT_TYPE,

   MENU_ITEM_FIND_TEXT,
   MENU_ITEM_FIND_TAG,
   MENU_ITEM_FIND_MODULE,

   MENU_ITEM_PREFS_EDIT,
   MENU_ITEM_PREFS_SAVE,

   MENU_ITEM_HELP_KEYS,
   MENU_ITEM_HELP_NOTES,
   MENU_ITEM_HELP_ABOUT,
   MENU_ITEM_HELP_SEARCH,
   //lv
   MENU_ITEM_EDIT_CUT,
   MENU_ITEM_EDIT_COPY,
   MENU_ITEM_EDIT_PASTE,
   
   MENU_ITEM_EDIT_UNDO,
   MENU_ITEM_EDIT_REDO,
   MENU_ITEM_EDIT_SELECT_ALL
} MENU_ITEM;

/*
 * Tag column layout enums
 */
enum
{
   TAG_COL_LAYOUT_TAG_TYPE_MODULE_LINE,
   TAG_COL_LAYOUT_TAG_MODULE_TYPE_LINE,
   TAG_COL_LAYOUT_MODULE_TAG_TYPE_LINE,
   TAG_COL_LAYOUT_MODULE_TYPE_TAG_LINE,

   TAG_COL_LAYOUT_TAG_MODULE_LINE		/* for clist containing results of a search */
};

/*
 * Dialog placement enums.
 */ 
enum
{
  /*
   * Saved into .gnome/hypersrc.
   */
   DIALOG_PLACEMENT_TOP_CORNER,
   DIALOG_PLACEMENT_BOTTOM_CORNER,
   DIALOG_PLACEMENT_MIDDLE,
   DIALOG_PLACEMENT_RESTORE,
   DIALOG_PLACEMENT_DEFAULT_WM  /* should have been first, too late to change now */
};

/*
 * Toolbar placement enums.
 */ 
enum
{
  /*
   * Saved into .gnome/hypersrc.
   */
   TOOLBAR_PLACEMENT_RIGHT = 0,		/* to right of menubar (0 for compatibility) */
   TOOLBAR_PLACEMENT_BELOW = 1		/* below menubar */
};

enum
{
   DONT_RELOAD = 0,
   DO_RELOAD   = 1
};

enum
{
   SRC_FILE_C,			/* C */
   SRC_FILE_CPLUSPLUS,	/* C++ */
   SRC_FILE_JAVA,		/* Java */
   SRC_FILE_PYTHON,		/* Python */
   SRC_FILE_PERL,		/* Perl */
   SRC_FILE_FORTH,		/* FORTH */
   SRC_FILE_ASM,		/* assembly */
   SRC_FILE_OTHER   
};

/* For passing to SwitchActiveTextWidget() */
enum
{
   SWITCH_PER_AUX_TEXT_KEY         = 0, /* old text widget behavior (DEPRECATED) */
   DONT_SWITCH_UNLESS_AUX_TEXT_KEY = 1  /* new text widget behavior */
};

enum
{
   DONT_APPLY_TREE_FONTS,
   DO_APPLY_TREE_FONTS
};

/* For passing to SearchClistWidget() */
enum
{
   SEEKING_ANY_TAG			= 0,
   SEEKING_FUNC_LIKE_TAG	= 1		/* funcs/macros/methods */
};

/* For passing to CreateNotebookPageWithModuleTree(). */
enum
{
   DONT_DECORATE	= 0,
   DO_DECORATE		= 1
};

/* For passing to SetSensitivityModuleFuncTrees(). */
enum
{
   DONT_HIDE_IF_INSENSITIVE	= 0,
        HIDE_IF_INSENSITIVE	= 1
};

/* Search method. */
enum
{
   SEARCH_NORMAL = 0,
   SEARCH_REGEX  = 1
};

/* Scope of regex matching. */
enum
{
   REGEX_SCOPE_LINE = 0,  /* limit matching to one line */
   REGEX_SCOPE_SPAN = 1   /* allow matching to span lines */
};

/*****************************************************************************
 * Function macros.
 *****************************************************************************/

#ifndef STREQ
#define STREQ( S1, S2 )			( strcmp( (S1), (S2) ) == 0 )
#endif

#ifndef STRNE
#define STRNE( S1, S2 )			( strcmp( (S1), (S2) ) != 0 )
#endif

#ifndef STREMPTY
#define STREMPTY( S )           ( ((S) == NULL) || ((S)[0] == '\0') )
#endif

#ifndef MEMEQ
#define MEMEQ( S1, S2, LEN )	( memcmp( (S1), (S2), (LEN) ) == 0 )
#endif

#ifndef MENNE
#define MEMNE( S1, S2, LEN )	( memcmp( (S1), (S2), (LEN) ) != 0 )
#endif

#ifndef MAX
#define MAX( A, B )             (((A) > (B)) ? (A) : (B))
#endif

#ifndef MIN
#define MIN( A, B )             (((A) < (B)) ? (A) : (B))
#endif

#define ELEMS( ARRAY )	        ( sizeof(ARRAY) / sizeof(ARRAY[0]) )

/* @return True if left or right parenthesis. */
#define IS_PARENTHESIS( C )     (((C) & ~1) == 40)

#define IS_EOL( CHAR )          ( ((CHAR)=='\n') || ((CHAR)=='\r') )

/*
 * Call Msg() for debug messages other than warnings/errors.
 */
#ifdef HYPERSRC_DEBUG
#define DebugMsg( format, args... )		\
		g_print( format , ## args )	,	\
		g_print( "\n" )
#else
#define DebugMsg( format, args... )
#endif

/*
 * Call StatusMsg() for non-debug messages enabled by -status.
 */
#define StatusMsg( format, args... )	\
	if ( UX(printStatusMsgs) )			\
		g_print(format , ## args )

/*
 * Call Warning() for when a warning is needed but program should continue.
 */
#define Warning( format, args... )			\
	fprintf( stderr, "*** WARNING: " )	,	\
	fprintf( stderr, format , ## args )	,	\
	fprintf( stderr, "\n" )

/*
 * Call WarningMalfunction() for internal errors, but program can continue.
 */
#define WarningMalfunction()	\
	fprintf( stderr, "*** INTERNAL ERROR: %s() malfunctioned, but continuing... \n", __FUNCTION__ )

/*
 * Print an error message.
 */
#define ErrorMsg( format, args... )			\
	fprintf( stderr, "*** ERROR: " )	,	\
	fprintf( stderr, format , ## args )	,	\
	fprintf( stderr, "\n" )
#define ErrorMsgCr()						\
	fprintf( stderr, "\n" )

/*
 * Print an error message and terminate.
 * (Avoid g_error() because it will dump core on Red Hat 6.2.)
 */
#define Error( format, args... )		\
	ErrorMsg( format , ## args )	,	\
	gtk_exit( 1 )

/*----------------------------  GNU gcc  -------------------------------------*/
#if __GNUC__
#define GCC_VERSION (__GNUC__*10000 + __GNUC_MINOR__*100 + __GNUC_PATCHLEVEL__)
#else
#define GCC_VERSION 0 /* if nothing will cause error on Visual C++ */
#endif

/*
 * Give branch hint to compiler.
 */
#if __GNUC__ >= 3
#define likely(x)	__builtin_expect((x),1)
#define unlikely(x)	__builtin_expect((x),0)
#else
#define likely(x) (x)
#define unlikely(x) (x)
#endif
#define EX(x) likely((x))	/* abbrev for expected */
#define UX(x) unlikely((x))	/* abbrev for unexpected */

/*
 * Tell compiler a var is unused.
 */
#if GCC_VERSION > 0 && GCC_VERSION >= 30100 /* if gcc-3.1 or later */
#define UNUSED __attribute__ ((unused))
#else
#define UNUSED
#endif
/*----------------------------  GNU gcc  -------------------------------------*/

#endif /* DEFINES_H */
